package org.monkeypuzzler.css;

import java.io.File;
import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;
import java.util.HashMap;
import java.util.Map;

import com.thoughtworks.xstream.XStream;

public class XStreamPersistenceStrategy implements PersistenceStrategy 
{
	static final XStream SERIALIZER;
	
	static {
		SERIALIZER = new XStream();
		SERIALIZER.alias("element", Element.class);
		SERIALIZER.alias("style", Style.class);
	}
	
	private File storeDir;
	private Map<String, File> storageMap = new HashMap<String, File>();
	
	public XStreamPersistenceStrategy(String storePath) 
	{
		storeDir = new File(storePath);
		storeDir.mkdirs(); //make sure we have a real path
	}
	
	public boolean exists(String locator, String identifier) 
	{
		return this.getSerializedElement(locator, identifier).exists();
	}

	public Element retrieve(String locator, String identifier) 
	{
		File serialed = this.getSerializedElement(locator, identifier);
		try
		{
			 return (Element)SERIALIZER.fromXML(new FileInputStream(serialed));
		}
		catch (FileNotFoundException e)
		{
			return null;
		}
		finally
		{
			//don't have to close the file? Huh.
		}
	}

	public void store(String locator, String identifier, Element element)
	{
		try 
		{
			File serialed = this.getSerializedElement(locator, identifier);
			System.out.println(serialed.getAbsolutePath());
			if (!serialed.exists())
				serialed.createNewFile();
			SERIALIZER.toXML(element, new FileOutputStream(serialed));
			System.out.println(SERIALIZER.toXML(element));
		}
		catch (IOException e)
		{
		    e.printStackTrace();
			//what to do, what to do. Fail the test, I guess?
			throw new AssertionError("Cannot write out file ["+e+"]");
		}
	}
	
	private File getIdentDir(String ident)
	{
		if (!this.storageMap.containsKey(ident))
		{
			File identDir = new File(this.storeDir, ident);
			identDir.mkdir();
			this.storageMap.put(ident, identDir);
		}
		return this.storageMap.get(ident);
	}

	private String getElementFileName(String locator)
	{
		return locator.concat(".xml");
	}
	
	private File getSerializedElement(String locator, String ident)
	{
		File dir = getIdentDir(ident);
		return new File(dir, getElementFileName(locator) );
	}
	
}
